﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Data.SqlClient;
using System.Drawing;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Windows.Forms;
using Common;

namespace TestingServer
{
    public partial class Form1 : Form
    {
        static IPEndPoint ipe;
        static UdpClient udp;

        public Form1()
        {
            InitializeComponent();
        }

        private void Debug(String debugText)
        {
            textBox1.Text += String.Format("{0}: {1}{2}", DateTime.Now.ToLongDateString(), debugText, Environment.NewLine);
        }

        private void StartServer()
        {
            byte[] sendBytes = new byte[4];
            
            UdpClient udpClientB = new UdpClient();
            udpClientB.Send(sendBytes, sendBytes.Length, "127.0.0.1", 2000);
        }

        private void button1_Click(object sender, EventArgs e)
        {
            StartServer();
        }

        private void button2_Click(object sender, EventArgs e)
        {
            DataOperate.OpenData(Configuration.DBServer, Configuration.DBName);

            try
            {
                Exception ex = DataOperate.BackupDatabase();

                if (ex == null)
                {
                    MessageBox.Show("Database backup sucessfully...");
                }
                else
                {
                    MessageBox.Show(ex.Message);
                }
            }
            finally
            {
                DataOperate.CloseData();
            }
        }

        private void button3_Click(object sender, EventArgs e)
        {
            IAsyncResult ia = udp.BeginReceive(ReceiveCallback, udp);
        }

        private void ReceiveCallback(IAsyncResult ar)
        {
            byte[] recvBytes = udp.EndReceive(ar, ref ipe);

            string debugData = String.Empty;
            foreach (byte Data in recvBytes) debugData += debugData != String.Empty ? "-" + Data.ToString() : Data.ToString();

            if (this.InvokeRequired)
                this.Invoke(new Action(() =>
                {
                    textBox1.Text += debugData + Environment.NewLine;
                }));
            else
            {
                textBox1.Text += debugData + Environment.NewLine;
            }			

            if (ar.IsCompleted) ar = udp.BeginReceive(ReceiveCallback, udp);
        }

        private void button4_Click(object sender, EventArgs e)
        {
            // http://www.dreamincode.net/forums/topic/156991-using-sqldependency-to-monitor-sql-database-changes/
            // http://www.codeproject.com/Articles/12335/Using-SqlDependency-for-data-change-events

            DataOperate.OpenData(Configuration.DBServer, Configuration.DBName);
            DataTable dtLog = new DataTable();

            using (SqlConnection conn = DataOperate.DataConnection)
            {
                SqlDataAdapter adapter = new SqlDataAdapter();
                adapter.SelectCommand = new SqlCommand("SELECT * FROM [dbo].[log] ORDER BY [x_created] DESC", conn);
                adapter.Fill(dtLog);

                dataGridView1.AutoGenerateColumns = false;
                dataGridView1.DataSource = dtLog;
            }
        }

        private void textBox1_DoubleClick(object sender, EventArgs e)
        {
            textBox1.Clear();
        }

        private void button5_Click(object sender, EventArgs e)
        {
            int ReceivePort = (Int32)Configuration.ReceivePort;

            try
            {
                ipe = new IPEndPoint(IPAddress.Any, ReceivePort);
            }
            catch (Exception exp)
            {
                textBox1.Text += exp.Message + Environment.NewLine;
            }

            udp = new UdpClient(ipe);
            udp.Client.ReceiveBufferSize = 8192;
            udp.Client.SendBufferSize = 8192;


            string[] test = textBox1.Text.Split('-');

            var bTest = new byte[test.Length];
            int i = 0;

            foreach (string item in test)
            {
                bTest[i] = Convert.ToByte(item);
                i++;
            }

            udp.Connect(ipe);
            udp.Send(bTest, bTest.Length);
        }
        
        
        private void SendResponse(byte rb1, byte rb2, byte rb3)
        {
            byte[] sendData = new byte[18];

            sendData[0] = 0x02;

            sendData[1] = rb1;
            sendData[2] = rb2;
            sendData[3] = rb3;

            sendData[16] = 0x03;

            PutCheckSum(0, sendData);

            udp.Connect(ipe);
            udp.Send(sendData, sendData.Length);
        }

       private void PutCheckSum(int Offset, byte[] Buf)
        {
            int chs = 0;

            for (int i = Offset; i < Buf.Length-1; i++)
            {
                chs = chs ^ Buf[i];
            }
            
           Buf[Buf.Length - 1] = Convert.ToByte(chs);
        }

       private void button6_Click(object sender, EventArgs e)
       {
           string[] test = textBox1.Text.Split('-');

           var bTest = new byte[test.Length];
           int i = 0;

           foreach (string item in test)
           {
               bTest[i] = Convert.ToByte(item);
               i++;
           }

           textBox2.Text = CheckSum(bTest) ? "ok" : "not ok";
       }

       private Boolean CheckSum(byte[] ReceiveBytes)
       {
           int Sum = 0;

           foreach (byte Data in ReceiveBytes)
           {
               Sum = Sum ^ Data;
           }

           return (Sum == 0);
       }

       private void button7_Click(object sender, EventArgs e)
       {
           string[] test = textBox1.Text.Split('-');

           var bTest = new byte[test.Length];
           int i = 0;

           foreach (string item in test)
           {
               bTest[i] = Convert.ToByte(item);
               i++;
           }

           PutCheckSum(0, bTest);
           textBox2.Text = bTest[bTest.Length-1].ToString();
       }

       private void button8_Click(object sender, EventArgs e)
       {
           string[] test = textBox1.Text.Split('-');

           var bTest = new byte[test.Length];
           int i = 0;

           foreach (string item in test)
           {
               bTest[i] = Convert.ToByte(item);
               i++;
           }

           byte[] recipeName = new byte[16];
           Buffer.BlockCopy(bTest, 4, recipeName, 0, 16);

           textBox2.Text = Encoding.ASCII.GetString(recipeName);
       }

       static private int BytesToInt(byte B1, byte B2)
       {
           return B1 * 256 + B2;
       }

       private void button9_Click(object sender, EventArgs e)
       {
           DataOperate.OpenData(Configuration.DBServer, Configuration.DBName);

           string[] test = textBox1.Text.Split('-');

           var bTest = new byte[test.Length];
           int i = 0;

           foreach (string item in test)
           {
               bTest[i] = Convert.ToByte(item);
               i++;
           }

           int[] Values = new int[38];
           int packetNumber = 0;
           string recipeIdentifier = String.Empty;

           if (bTest.Length == 98)
           {
               packetNumber = BytesToInt(bTest[2], bTest[3]);

               byte[] recipeName = new byte[16];
               Buffer.BlockCopy(bTest, 4, recipeName, 0, 16);
               recipeIdentifier = Encoding.ASCII.GetString(recipeName);

               for (int j = 0; j < 38; j++)
               {
                   int idx = 20 + 2 * j;

                   try
                   {
                       Values[j] = BytesToInt(bTest[idx], bTest[idx + 1]);
                   }
                   catch (Exception ex)
                   {
                       Values[j] = 0;
                       //DataOperate.WriteToDbLog("Exp", ex.Message);
                   }
               }
           }

           DataOperate.WriteValues(Convert.ToChar(bTest[1]), packetNumber, recipeIdentifier, Values);
       }
    }
}